package com.wbdca.crawler.common;

import com.google.gson.JsonElement;
import com.google.gson.JsonNull;
import com.google.gson.stream.JsonWriter;
import com.wbdca.crawler.entity.Event;
import com.wbdca.crawler.entity.Organization;
import com.wbdca.crawler.entity.Repository;
import com.wbdca.crawler.entity.User;

import java.io.File;
import java.io.FileWriter;
import java.io.IOException;
import java.util.ArrayList;
import java.util.Map;

public class JsonFileWriter {
    private static JsonWriter jsonWriter;
    public static void write(Object obj){
        if(obj == null){
            return ;
        }
        User user = (User) obj;
        File file = new File("./" + user.getLogin() + ".json");
        try {
            jsonWriter = new JsonWriter(new FileWriter(file));
            jsonWriter.setIndent("\t");
            writeUser(user);
        } catch (IOException e) {
            throw new RuntimeException(e);
        } finally {
            try {
                assert jsonWriter != null;
                jsonWriter.close();
            } catch (IOException e) {
                throw new RuntimeException(e);
            }
        }
    }

    private static void writeUser(User user) throws IOException {
        jsonWriter.beginObject();
        jsonWriter.name("login").value(user.getLogin());
        jsonWriter.name("avatarUrl").value(user.getAvatarUrl());
        jsonWriter.name("name").value(user.getName());
        jsonWriter.name("followers").value(user.getFollowers());
        jsonWriter.name("following").value(user.getFollowing());
        jsonWriter.name("repos");
        writeRepositories(user.getRepositories());
        jsonWriter.name("organizations");
        writeOrganizations(user.getOrganizations());
        jsonWriter.name("events");
        writeEvents(user.getEvents());
        jsonWriter.endObject();
    }

    private static void writeRepositories(ArrayList<Repository> repositories) throws IOException {
        jsonWriter.beginArray();
        for (Repository repository : repositories){
            writeRepository(repository);
        }
        jsonWriter.endArray();
    }

    private static void writeRepository(Repository repository) throws IOException {
        jsonWriter.beginObject();
        jsonWriter.name("name").value(repository.getName());
        jsonWriter.name("forks").value(repository.getForks());
        jsonWriter.name("open_issues").value(repository.getOpenIssues());
        jsonWriter.name("forks").value(repository.getWatchers());
        jsonWriter.name("license").value(repository.getLicense());

        jsonWriter.name("languages");
        jsonWriter.beginObject();
        for(Map.Entry<String, Integer> entry : repository.getLanguages().entrySet()){
            jsonWriter.name(entry.getKey()).value(entry.getValue());
        }
        jsonWriter.endObject();

        jsonWriter.name("topics");
        jsonWriter.beginArray();
        for(String topic : repository.getTopics()){
            jsonWriter.value(topic);
        }
        jsonWriter.endArray();

        jsonWriter.endObject();

    }

    private static void writeOrganizations(ArrayList<Organization> organizations) throws IOException {
        jsonWriter.beginArray();
        for(Organization org : organizations){
            writeOrganization(org);
        }
        jsonWriter.endArray();
    }

    private static void writeOrganization(Organization org) throws IOException {
        jsonWriter.beginObject();
        jsonWriter.name("login").value(org.getLogin());
        jsonWriter.name("description").value(org.getDescription());
        jsonWriter.endObject();
    }

    private static void writeEvents(ArrayList<Event> events) throws IOException {
        jsonWriter.beginArray();
        for(Event event : events) {
            writeEvents(event);
        }
        jsonWriter.endArray();
    }

    private static void writeEvents(Event event) throws IOException {
        jsonWriter.beginObject();
        jsonWriter.name("type").value(event.getType());
        jsonWriter.name("created_at").value(event.getCreatedAt());
        jsonWriter.endObject();
    }

}
